package edu.bbu.commonproject.desktop.gui.view.swing.file.lister;

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.dnd.DnDConstants;
import java.awt.dnd.DropTarget;
import java.awt.dnd.DropTargetListener;
import java.io.File;
import java.util.TooManyListenersException;

import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.SwingUtilities;

import edu.bbu.commonproject.desktop.gui.view.swing.file.lister.components.LDirectory;
import edu.bbu.commonproject.desktop.gui.view.swing.file.lister.components.LFile;
import edu.bbu.commonproject.desktop.gui.view.swing.file.lister.components.LParentDirectory;
import edu.bbu.commonproject.desktop.gui.view.swing.file.lister.components.Listable;
import edu.bbu.commonproject.desktop.gui.view.swing.file.lister.utils.GeneralDialog;
import edu.bbu.commonproject.desktop.gui.view.swing.file.lister.utils.WrapLayout;

/**
 * The panel, for listing the files from the local file system.
 */
public class LocalFileListPanel extends JPanel implements FileLister
{	
	/** The current diectory. */
	private String currentDirectory = "";
	
	/** The document panel. */
	private JPanel documentPanel;
	
	/** The scroll panel. */
	private JScrollPane scrollPane;
	
	/** The control panel. */
	private LocalFilesControlPanel controlPanel;
	
	/** The selected object in the list. */
	private Listable selectedObject;
	
	/** The local filelist panel. */
	private DropTarget dropTarget;
	
	/**
	 * The constructor.
	 */
	public LocalFileListPanel()
	{
		dropTarget = new DropTarget();
		dropTarget.setActive(true);
		dropTarget.setComponent(this);
		dropTarget.setDefaultActions(DnDConstants.ACTION_COPY);
		
		documentPanel = new JPanel();
		documentPanel.setBackground(Color.WHITE);
		documentPanel.setLayout(new WrapLayout(WrapLayout.LEFT));
		
		scrollPane = new JScrollPane(documentPanel);
		scrollPane.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS);
		scrollPane.getVerticalScrollBar().setUnitIncrement(35);
		
		controlPanel = new LocalFilesControlPanel();
		
		this.setLayout(new BorderLayout());
		this.setPreferredSize(new Dimension(550, 500));
		
		this.add(scrollPane, BorderLayout.CENTER);
		this.add(controlPanel, BorderLayout.NORTH);
	}
	
	/**
	 * Setting the selected object of the lister.
	 * @param selectedObject the new selected object.
	 */
	public void setSelectedListItem(Listable selectedObject)
	{
		this.selectedObject = selectedObject;
	}
	
	/**
	 * Getting the selected object of the lister.
	 * @return the currently selected object or null if there is no seleccted object.
	 */
	public Listable getSelectedListItem()
	{
		return this.selectedObject;
	}
	
	/**
	 * Setting the current directory and updates the control panel too.<br>
	 * If the currentDirectory parameter dont ends witd the default system
	 * separator, this will be appanded to the end of it.
	 * @param currentDirectory the current directory.
	 */
	public void setCurrentPath(final String currentDirectory)
	{
		if(currentDirectory.endsWith(File.separator))
		{
			this.currentDirectory = currentDirectory;
		}
		else 
		{
			this.currentDirectory = currentDirectory + File.separator;
		}
		
		SwingUtilities.invokeLater(new Runnable()
		{
			public void run()
			{
				controlPanel.getCurrentDirectoryLabel().setText("Local: " + currentDirectory);
			}
		});
	}
	
	/**
	 * Getting the current directry.
	 * @return the current directory.
	 */
	public String getCurrentPath()
	{
		return currentDirectory;
	}
	
	/**
	 * Append to the current directory.<br>
	 * This will update the control panel too.<br>
	 * If the new directory parameter dont ends with the default system 
	 * separator, the it will be appanded to the end of current directory.
	 * @param directory the directory name.
	 */
	public void appendCurrentPath(String directory)
	{
		if(directory.endsWith(File.separator))
		{
			this.currentDirectory = currentDirectory + directory;
		}
		else 
		{
			this.currentDirectory = currentDirectory + directory + File.separator;
		}
		
		SwingUtilities.invokeLater(new Runnable()
		{
			public void run()
			{
				controlPanel.getCurrentDirectoryLabel().setText("Local: " + currentDirectory);
			}
		});
	}
	
	/**
	 * Clearing the current directory.
	 * The new directory is an empty string.
	 */
	public void clearCurrentPath()
	{
		this.currentDirectory = "";
		
		SwingUtilities.invokeLater(new Runnable()
		{
			public void run()
			{
				controlPanel.getCurrentDirectoryLabel().setText("Local: ");	
			}
		});
	}
	
	public boolean isCurrentPathCleared()
	{
		return currentDirectory.equals("");
	}
	
	/**
	 * Clearing all the files and folders from the document panel.
	 */
	public void clearDocumentPanel()
	{
		documentPanel.removeAll();
		selectedObject = null;
	}
	/**
	 * Updating the document panel.
	 * This update is a revalidate() and a repaint() call of the document panel.
	 */
	public void refreshDocumentPanel()
	{
		documentPanel.revalidate();
		documentPanel.repaint();
	}
	
	/**
	 * Append a new parent directory to the list. If there was set the selected object, it was cleared by setting it to null.
	 * @param parent the parent directory.
	 */
	public void addParentDirectory(LParentDirectory parent)
	{
		documentPanel.add(parent);
		selectedObject = null;
	}	
	
	/**
	 * Append a new directory to the list. If there was set the selected object, it was cleared by setting it to null.
	 * @param directory the new directory.
	 */
	public void addDirectory(LDirectory directory)
	{
		directory.setFileLister(this);
		documentPanel.add(directory);
		selectedObject = null;
	}
	
	/**
	 * Append a new file to the list. If there was set the selected object, it was cleared by setting it to null.
	 * @param file the new file.
	 */
	public void addFile(LFile file)
	{
		file.setFileLister(this);
		documentPanel.add(file);
		selectedObject = null;
	}
	
	/**
	 * Getting the control panel.
	 * @return the control panel.
	 */
	public LocalFilesControlPanel getControlPanel()
	{
		return controlPanel;
	}
	
	/**
	 * It adds the drop target listener.
	 * @param dropTargetListener the drop target listener.
	 */
	public void addDropTargetListener(DropTargetListener dropTargetListener)
	{
		try
		{
			dropTarget.addDropTargetListener(dropTargetListener);
		}
		catch (TooManyListenersException e) { }
	}
}

